#!/usr/bin/python3
# -*- coding:utf-8 -*-
import time

from qturboframe.lib.utils.by import By
from BladeFerm.hui_app.hui_lib.form import Form as HuiForm
from qturboframe.lib.report.log import logger
from qturboframe.lib.webdriver.exceptions import SeleniumError
from qturboframe.public_ui.__common__ import deal_form_data
from BladeFerm.hui_app.hui_lib.select import Select
from BladeFerm.hui_app.hui_lib.input_type import InputType

class Form(HuiForm):
    '''
    form表单填入
    '''

    def button_click_until_loading(self, text, time_out=30):
        '''
        统一资讯云专用，按钮处于加载中状态时，会等待加载完成后进行点击
        适用范围 当数据加载时 按钮进入h-btn-loading状态 处于加载中状态
        :param text: 按钮名称：查询、重置、更多、简单等
        :time_out: 超时时间
        :return:
        '''
        begin = int(time.time())
        now = begin
        button_element = None
        while (now-begin) < time_out:
            button_element = self.element.find_element_by_attribute(
                By.CSS_SELECTOR, 'button.h-btn', 'text:' + text,
                timeout=1)
            if "h-btn-loading" in button_element.get_attribute("class"):
                now = int(time.time())
                logger.info(time.time())
                time.sleep(1)
            else:
                break
        else:
            logger.error("等待超时")
        button_element.click()

    def __TERM_ADD__(self, key, value, element):
        '''
        仅仅可用于资讯云
        Args:
            key:
            value:
            element:

        Returns:

        '''
        logger.info("{}进入处理组合控件逻辑".format(key))
        #following-sibling::div[@class=\'h-form-item-content\']/
        add = element.find_element_by_attribute(
            'xpath', '../span[@class=\'cloudiconfont iconpopup_2\']', timeout=3
        )
        for i in range(0,len(value)):
            logger.info("第{}条记录写入".format(i))
            if i != 0:
                logger.info("数据未写完，点击新增")
                add.click()
            names = element.find_elements_by_attribute(
                'xpath', '../div/div/div/div[@class=\'input h-select h-select-single\']', timeout=3)
            e_mails=element.find_elements_by_attribute(
                'xpath', '../div/div/div/div[@class=\'h-input-wrapper h-input-type\']', timeout=3)
            select = Select(names[len(names)-1])
            select.set_value_for_single(value[i]["名称"])
            logger.info("写入{} {}行 名称{}".format(key,i,value[i]["名称"]))
            input_type=InputType(e_mails[len(e_mails)-1])
            input_type.set_value(value[i]["邮箱"])
            logger.info("写入{} {}行 邮箱{}".format(key, i, value[i]["邮箱"]))

    def auto_fill(self, inputdata):
        '''
        hui表单自动填充功能

        :Args:
         inputdata: 输入数据，需要定位的表单抬头和待输入文本
            input_data_key  :  输入格式支持2种。
            1. 直接写key值；
            2.key值后指定控件序号，'#'连接。如 'key#2'，表示第2个包含key的控件
         input_data_value:  输入格式支持3种。
            1. 直接写value值；
            2.value值后指定检查类型，'#'连接
                - 'value#R': 表示检查value值输入控件是否只读类型
                - 'value#D': 表示检查value值输入控件是否存在默认值
                - 'value#M': 表示检查value值输入控件是否是必填项
            3.多选框填写值时，用英文 逗号 分割。例如： '中信银行,上海银行'
            4.日期填写格式：单个日期: '2022-05企业日志查询-18' 范围日期格式： '2022-05企业日志查询-18 - 2022-05企业日志查询-23' (中间的分割符号是：' - ')

        :Raises:
            SeleniumError: 表单填充或校验出错

        :Example:
         - 例: form.auto_fill({'姓名':'admin','年龄':'25','工号':'asdf1234'})
        '''
        logger.info("表单填写开始")
        try:
            for input_key, input_value in inputdata.items():
                if input_value == '':
                    continue
                if type(input_value) == list:
                    label_elements = self.element.find_elements_by_attribute(
                        'class name', 'h-form-item-label', 'text:' + input_key,
                        timeout=self.timeout)
                    if len(label_elements) == 0:
                        raise SeleniumError("没有找到“{}”控件".format(input_key))
                    logger.info(f'{input_key}:{input_value} 判断为组合控件')
                    self.__TERM_ADD__(input_key, input_value, label_elements[0])
                else:
                    key, value, flag, label_seq = deal_form_data(input_key, input_value)
                    label_elements = self.element.find_elements_by_attribute(
                        'class name', 'h-form-item-label', 'text:' + key,
                        timeout=self.timeout)
                    if len(label_elements) == 0:
                        raise SeleniumError("没有找到“{}”控件".format(key))
                    label = label_elements[label_seq - 1]
                    self.__foud_div_type(label, input_key, input_value)
                    # 确定类型
                    control_type_list = self.__confirm_type()
                    if len(control_type_list) > 1:
                        templist = list()
                        for i in range(0, len(control_type_list)):
                            templist.append([value[i]])
                        value = templist
                    elif len(control_type_list) == 0:
                        continue
                    else:
                        value = [value]
                    # 识别控件并执行
                    for i, control_type in enumerate(control_type_list):
                        # 根据控件类型选择控件操作
                        if control_type == self.__INPUT_TYPE_CLASS:
                            self.__deal_input_type(key, value[i], flag)
                        elif control_type == self.__INPUT_NUMBER_CLASS:
                            self.__deal_input_number(key, value[i], flag)
                        elif control_type == self.__TYPE_FIELD_CLASS:
                            self.__deal_type_field(key, value[i], flag)
                        elif control_type == self.__SELECT_SINGLE_CLASS:
                            self.__deal_select_single(key, value[i], flag)
                        elif control_type == self.__SELECT_MULTIPLE_CLASS:
                            self.__deal_select_multiple(key, value[i], flag)
                        elif control_type == self.__SELECT_TREE_SINGLE_CLASS:
                            self.__deal_select_tree_single(key, value[i], flag)
                        elif control_type == self.__SELECT_TREE_MULTIPLE_CLASS:
                            self.__deal_select_tree_multiple(key, value[i], flag)
                        elif control_type == self.__SELECT_TABLE_SINGLE_CLASS:
                            self.__deal_select_table_single(key, value[i], flag)
                        elif control_type == self.__RADIO_CLASS:
                            self.__deal_radio(key, value[i], flag)
                        elif control_type == self.__CHECKBOX_CLASS:
                            self.__deal_checkbox(key, value[i], flag)
                        elif control_type == self.__CALENDAR_CLASS:
                            i_icon = self._elements.find_element_by_attribute(
                                'css selector', 'div.h-date-picker-rel i.h-icon', timeout=self.timeout)
                            icon_class_list = i_icon.get_attribute('class').split(' ')
                            if 'h-icon-time' in icon_class_list:
                                self.__deal_timer(key, value[i], flag)
                            elif 'h-icon-activity' in icon_class_list:
                                self.__deal_calendar(key, value[i], flag)
        except Exception as msg:
            raise SeleniumError(str(msg))
        logger.info("表单填写结束")

    def del_form(self, element, data: dict):
        '''
        资讯云产品专用 团队管理和客户管理 点击修改后表格的删除节点处理，一般是由update_form自动调用的
        arg :element 节点
            data 由于定位删除位置的数据 {职位：xxx，序号:xxx}
        '''
        index =data["序号"]
        logger.info("删除{}数据".format(data["职位"]))
        subs=element.find_elements_by_attribute(
            'xpath', '../div/span[@class=\'cloudiconfont iconpopup_1\']', timeout=3
        )
        if len(subs) ==0:
            logger.info("没有删除按钮，删除失败")
        elif index >len(subs):
            logger.info("删除序号大于表单中信息，删除失败")
        else:
            subs[index-1].click()
            logger.info("点击{}个删除按钮".format(index))

    def add_form(self,element,data):
        '''
        资讯云产品专用 团队管理和客户管理 点击修改后表格的增加节点处理，一般是由update_form自动调用的
        arg :element 节点
            data 由于定位增加位置的数据和增加数据 {职位：xxx，名称:xxx，邮箱：xxx}
        '''
        logger.info("新增{}数据".format(data["职位"]))
        add = element.find_element_by_attribute(
            'xpath', '../span[@class=\'cloudiconfont iconpopup_2\']', timeout=3
        )
        add.click()
        names = element.find_elements_by_attribute(
            'xpath', '../div/div/div/div[@class=\'input h-select h-select-single\']', timeout=3)
        e_mails = element.find_elements_by_attribute(
            'xpath', '../div/div/div/div[@class=\'h-input-wrapper h-input-type\']', timeout=3)
        logger.info(len(names))
        select = Select(names[len(names)-1])
        select.set_value_for_single(data["名称"])
        logger.info("写入{}  名称{}".format(data["职位"],data["名称"]))
        input_type = InputType(e_mails[len(e_mails)-1])
        input_type.set_value(data["邮箱"])
        logger.info("写入{} 邮箱{}".format(data["职位"],data["邮箱"]))

    def update_form(self,input_data):
        '''
        资讯云产品专用 团队管理和客户管理 点击修改后表单的操作
        arg :input_data 操作数据 由list构成如下
            [{操作: 删,职位: 负责人,序号: 1},{操作: 增,职位: 负责人,名称: 系统管理员,邮箱: 666@123.com}]
        '''
        logger.info("开始修改表单")
        for operation in input_data:
            key =operation["职位"]
            #找到对应的位置
            label_elements = self.element.find_elements_by_attribute(
                'class name', 'h-form-item-label', 'text:' + key,
                timeout=self.timeout)
            if len(label_elements) == 0:
                raise SeleniumError("没有找到“{}”控件".format(key))
            if operation["操作"] == "删":
                self.del_form(label_elements[0], operation)
            elif operation["操作"] == "增":
                self.add_form(label_elements[0], operation)
            else:
                pass
        logger.info("修改结束")